package com.zkthink.ceres.product.controller;

import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import org.springframework.util.CollectionUtils;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.zkthink.base.R;
import com.zkthink.base.controller.SuperController;
import com.zkthink.base.request.PageParams;
import com.zkthink.dozer.DozerUtils;
import com.zkthink.log.annotation.SysLog;
import com.zkthink.security.annotation.PreAuth;
import com.zkthink.ceres.product.converter.LogisticsBeanConverter;
import com.zkthink.ceres.product.dto.LogisticsPageDTO;
import com.zkthink.ceres.product.dto.LogisticsSaveDTO;
import com.zkthink.ceres.product.dto.LogisticsUpdateDTO;
import com.zkthink.ceres.product.entity.Logistics;
import com.zkthink.ceres.product.entity.LogisticsDetail;
import com.zkthink.ceres.product.service.LogisticsDetailService;
import com.zkthink.ceres.product.service.LogisticsService;
import com.zkthink.ceres.product.vo.LogisticsPageVO;
import com.zkthink.ceres.product.vo.LogisticsVO;

import cn.hutool.core.bean.BeanUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;

/**
 * <p>
 * 前端控制器 物流设置
 * </p>
 *
 * @author vivi.huang
 * @date 2020-05-16
 */
@Slf4j
@Validated
@RestController
@RequestMapping("/logistics")
@Api(value = "Logistics", tags = "物流设置")
@AllArgsConstructor
// @PreAuth(replace = "logistics:")
public class LogisticsController
    extends SuperController<LogisticsService, Long, Logistics, LogisticsPageDTO, LogisticsSaveDTO, LogisticsUpdateDTO> {

    private LogisticsBeanConverter converter;

    private LogisticsDetailService detailService;

    private LogisticsService logisticsService;

    private DozerUtils dozerUtils;

    /**
     * Excel导入后的操作
     *
     * @param list
     */
    @Override
    public R<Boolean> handlerImport(List<Map<String, String>> list) {
        List<Logistics> logisticsList = list.stream().map((map) -> {
            Logistics logistics = Logistics.builder().build();
            // TODO 请在这里完成转换
            return logistics;
        }).collect(Collectors.toList());

        return R.success(baseService.saveBatch(logisticsList));
    }

    /**
     * 查询
     *
     * @param id
     *            主键id
     * @return 查询结果
     */
    @ApiImplicitParams({@ApiImplicitParam(name = "id", value = "主键", dataType = "long", paramType = "query"),})
    @ApiOperation(value = "查询物流明细", notes = "查询物流明细")
    @GetMapping("/detail/{id}")
    @SysLog("'查询物流明细:' + #id")
    @PreAuth("hasPermit('{}view')")
    public R<LogisticsVO> getLogisticsVO(@PathVariable Long id) {
        Logistics logistics = getBaseService().getById(id);
        List<LogisticsDetail> logisticsDetailList = detailService.findLogisticsDetailList(Arrays.asList(id));
        return R.success(converter.convertToLogisticsVO(logistics, logisticsDetailList));
    }

    /**
     * 新增
     *
     * @param logisticsSaveDTO
     *            保存参数
     * @return 实体
     */
    @ApiOperation(value = "新增")
    @PostMapping
    @SysLog(value = "新增", request = false)
    @PreAuth("hasPermit('{}add')")
    @Override
    public R<Logistics> save(@RequestBody @Validated LogisticsSaveDTO logisticsSaveDTO) {
        Logistics logistics = BeanUtil.toBean(logisticsSaveDTO, getEntityClass());
        getBaseService().save(logistics);
        List<LogisticsDetail> logisticsDetails =
            converter.covertToLogisticsDetailList(logistics.getId(), logisticsSaveDTO.getLogisticsDetailDTOList());
        detailService.saveBatch(logisticsDetails);
        return R.success(logistics);
    }

    /**
     * 修改
     *
     * @param logisticsUpdateDTO
     * @return
     */
    @ApiOperation(value = "修改")
    @PutMapping
    @SysLog(value = "'修改:' + #updateDTO?.id", request = false)
    @PreAuth("hasPermit('{}update')")
    @Override
    public R<Logistics> update(LogisticsUpdateDTO logisticsUpdateDTO) {
        Logistics logistics = BeanUtil.toBean(logisticsUpdateDTO, getEntityClass());
        getBaseService().updateById(logistics);
        List<LogisticsDetail> logisticsDetails =
            converter.covertToLogisticsDetailList(logistics.getId(), logisticsUpdateDTO.getLogisticsDetailDTOList());

        //修改明细，先删后增
        detailService.removeByLogisticsId(logisticsUpdateDTO.getId());
        detailService.saveBatch(logisticsDetails);
        return R.success(logistics);
    }

    /**
     * 分页查询物流明细
     *
     * @param params
     * @return
     */
    @ApiOperation(value = "分页列表查询物流明细")
    @PostMapping(value = "/detail/page")
    @SysLog(value = "'分页列表查询:第' + #params?.current + '页, 显示' + #params?.size + '行'", response = false)
    @PreAuth("hasPermit('{}view')")
    public R<IPage<LogisticsPageVO>> pageLogisticsDetail(@RequestBody @Validated PageParams<LogisticsPageDTO> params) {
        // 处理参数
        IPage<Logistics> page = params.getPage();

        query(params, page, null);

        List<LogisticsDetail> logisticsDetails = detailService
            .findLogisticsDetailList(page.getRecords().stream().map(Logistics::getId).collect(Collectors.toList()));

        Map<Long, List<LogisticsDetail>> map =
            logisticsDetails.stream().collect(Collectors.groupingBy(LogisticsDetail::getLogisticsId));

        IPage<LogisticsPageVO> pageVO = params.getPage();
        pageVO.setTotal(page.getTotal());
        pageVO.setRecords(page.getRecords().stream().map(r -> {
            return dozerUtils.map(r, LogisticsPageVO.class);
        }).collect(Collectors.toList()));

        pageVO.getRecords().forEach(r -> {
            List<LogisticsDetail> subList = map.get(r.getId());
            if (!CollectionUtils.isEmpty(subList)) {
                r.setRegionList(subList.stream().map(LogisticsDetail::getRegion).collect(Collectors.toList()));
            }
        });

        return success(pageVO);
    }

    /**
     * 删除方法
     *
     * @param ids
     * @return
     */
    @ApiOperation(value = "删除")
    @DeleteMapping
    @ApiImplicitParams({
            @ApiImplicitParam(name = "ids[]", value = "主键id", dataType = "array", paramType = "query"),
    })
    @SysLog("'删除:' + #ids")
    @PreAuth("hasPermit('{}delete')")
    @Override
    public R<Boolean> delete(@RequestParam("ids[]") List<Long> ids) {
        logisticsService.removeLogisticsAndDetail(ids);
        return R.success();

    }


}
